package com.zeronx.utils;

import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.MessageSource;
import org.springframework.http.HttpOutputMessage;
import org.springframework.http.converter.HttpMessageNotWritableException;
import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter;
import org.springframework.web.servlet.i18n.CookieLocaleResolver;

import javax.servlet.http.HttpServletRequest;
import java.io.IOException;
import java.lang.reflect.Field;
import java.lang.reflect.Type;
import java.util.Locale;

/**
 * @author foreee on 2017/3/30.
 * @version 1.0
 */
//@Component
public class MyJsonMessageConverter extends MappingJackson2HttpMessageConverter {

    @Autowired
    private HttpServletRequest request;
    @Autowired
    private MessageSource messageSource;

    public static final String LOCALE_REQUEST_ATTRIBUTE_NAME = CookieLocaleResolver.class.getName() + ".LOCALE";

    @Override
    protected void writeInternal(Object object, HttpOutputMessage outputMessage) throws IOException, HttpMessageNotWritableException {
//        //使用Jackson的ObjectMapper将Java对象转换成Json String
//        outputMessage.getBody().write(result.getBytes("UTF-8"));
        // 通过将object 转为 json 然后解析 #{xxx.xxx} 可能会出现的问题：如果返回的字段值中存在 "#{" 或 "}" 而没有 转义 则会出现问题
//        String result = toI18n(object);
//        // 通过反射解析 #{xxx.xxx} 实现比较麻烦，因为可能存在多种多种多层嵌套的对象，如：list[] , map , 等等
////        reflectToI18n(object);
        System.out.println("++++++++++++++++++++++++++++++++++++++++++");
//        Object object1= objectMapper.readValue(result,object.getClass());
        super.writeInternal(object, outputMessage);
    }

    @Override
    protected void writeInternal(Object object, Type type, HttpOutputMessage outputMessage) throws IOException, HttpMessageNotWritableException {
        System.out.println("============================================");
        String result = toI18n(object);
//        outputMessage.getBody().write(result.getBytes("UTF-8"));
//        objectMapper.disable(SerializationFeature.FAIL_ON_EMPTY_BEANS);
        Object object1= objectMapper.readValue(result,object.getClass());
        super.writeInternal(object1, type, outputMessage);
    }

    /**
     * 没有实现
     * @param object
     */
    private void reflectToI18n(Object object) {
        Locale locale = (Locale) request.getAttribute(LOCALE_REQUEST_ATTRIBUTE_NAME);
        Class clazz = object.getClass();
        Field[] fields = clazz.getDeclaredFields();
        for (int i = 0; i < fields.length; i++) {
            fields[i].setAccessible(true);
            String properties = fields[i].getName();
            try {
                Object ov = fields[i].get(object);
                String val = messageSource.getMessage(properties, null,  "", locale);
                fields[i].set(object, val);
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }
        }
    }

    private String toI18n(Object object) throws IOException, HttpMessageNotWritableException {
        //使用Jackson的ObjectMapper将Java对象转换成Json String
//        ObjectMapper mapper = new ObjectMapper();
        String json = objectMapper.writeValueAsString(object);
        Locale locale2 = (Locale) request.getAttribute(LOCALE_REQUEST_ATTRIBUTE_NAME);
        GenericTokenParserUtil rj = new GenericTokenParserUtil("#{", "}", locale2, messageSource);
        return rj.parse(json);
    }

}
//在这之后还需要将这个自定义的转换器配置到Spring中，这里通过重写WebMvcConfigurer中的configureMessageConverters方法添加自定义转换器：
//    //添加自定义转换器
//    @Override
//    public void configureMessageConverters(List> converters) {
//        converters.add(mappingJackson2HttpMessageConverter());
//        super.configureMessageConverters(converters);
//    }